package com.itlong.cloud.operate.service.impl;

import com.alibaba.fastjson.JSON;
import com.alibaba.fastjson.JSONArray;
import com.alibaba.fastjson.JSONObject;
import com.itlong.cloud.POJO.DTO.operate.OperateProductTypeManageGetDTO;
import com.itlong.cloud.POJO.PO.AssignmentProductInfoPO;
import com.itlong.cloud.POJO.PO.AssignmentProductModelRelationPO;
import com.itlong.cloud.POJO.PO.OperateUserInfoPO;
import com.itlong.cloud.POJO.PO.OperationSpecialLogPO;
import com.itlong.cloud.POJO.VO.MessageVO;
import com.itlong.cloud.POJO.VO.operate.OperateAssignProductModelRelationGetVO;
import com.itlong.cloud.POJO.VO.operate.OperateProductTypeManageGetVO;
import com.itlong.cloud.PlatformConstants;
import com.itlong.cloud.enumerate.DataStatusEnum;
import com.itlong.cloud.enumerate.FeeTypeEnum;
import com.itlong.cloud.enumerate.ecode.BaseErrorCodeEnum;
import com.itlong.cloud.enumerate.ecode.OperateErrorCodeEnum;
import com.itlong.cloud.operate.dao.IOperateProductTypeManageDao;
import com.itlong.cloud.operate.service.IOperateProductTypeManageService;
import com.itlong.cloud.utils.data.handler.SqlUtil;
import com.itlong.cloud.utils.page.Page;
import com.itlong.cloud.utils.random.LogicIdUtil;
import com.itlong.cloud.utils.words.StringHandlerUtil;
import org.apache.commons.lang.StringUtils;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;

import java.util.*;

/**
 * <desc>
 *      运营-产品类型管理服务层接口实现类
 * </desc>
 *
 * @createDate 2020/12/03
 */
@Service
public class OperateProductTypeManageServiceImpl implements IOperateProductTypeManageService {

    private static final Logger LOG = LoggerFactory.getLogger(OperateProductTypeManageServiceImpl.class);

    @Autowired
    private IOperateProductTypeManageDao iOperateProductTypeManageDao;

    /**
     * <desc>
     *      分页获取任务书产品类型信息
     * </desc>
     *
     * @param operateProductTypeManageGetDTO 获取任务书产品类型信息DTO
     * @return 分页任务书产品类型信息
     * @author pengwei
     * @createDate 2020/12/03
     */
    @Override
    public Page<OperateProductTypeManageGetVO> getPage(OperateProductTypeManageGetDTO operateProductTypeManageGetDTO) throws Exception{
        if (StringUtils.isBlank(operateProductTypeManageGetDTO.getOrderColumn())) {
            operateProductTypeManageGetDTO.setOrderColumn("createTime");
            operateProductTypeManageGetDTO.setOrderRule("DESC");
        }
        if(operateProductTypeManageGetDTO.getOrderColumn().equals("order")){
            operateProductTypeManageGetDTO.setOrderColumn("`order`");
        }
        Map<String, Object> params = SqlUtil.convertBeanToMapParams(operateProductTypeManageGetDTO);
        Page<OperateProductTypeManageGetVO> page = new Page<>();
        page.getPage().setPageSize(operateProductTypeManageGetDTO.getPageSize());
        page.getPage().setCurrentPage(operateProductTypeManageGetDTO.getCurrentPage());
        params.put("startSlip", page.getPage().getStartSlip());
        params.put("pageSize", page.getPage().getPageSize());
        List<OperateProductTypeManageGetVO> operateProductTypeManageVOList = iOperateProductTypeManageDao.getPage(params);
        page.setRows(operateProductTypeManageVOList, iOperateProductTypeManageDao.getRecordCount(params));
        return page;
    }

    /**
     * <desc>
     *      获取任务书产品类型详情
     * </desc>
     *
     * @param dto 获取任务书产品类型详情DTO
     * @return 任务书产品类型信息详情
     * @author pengwei
     * @createDate 2020/12/03
     */
    @Override
    public  OperateProductTypeManageGetVO  getOne(OperateProductTypeManageGetDTO dto) throws Exception{
        OperateProductTypeManageGetVO  vo   =  iOperateProductTypeManageDao.getOne(dto);
        List<OperateAssignProductModelRelationGetVO>   relationList = iOperateProductTypeManageDao.getRelatedProcModelList(dto.getAssignmentProcId());
        if (!relationList.isEmpty()){
            this.assembleModelData(relationList);
        }
        vo.setRelationList(relationList);
        return   vo;
    }

    /**
     * <desc>
     *      任务书产品类型信息删除
     * </desc>
     *
     * @param dto 任务书产品类型dto
     * @return 任务书产品类型删除
     * @author pengwei
     * @createDate 2020/12/03
     */
    @Override
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public Integer  delete(OperateProductTypeManageGetDTO dto) throws Exception{
        Date nowTime = new Date();
        Integer count = iOperateProductTypeManageDao.delete(dto);

        // 删除任务书产品类型中间表明细数据
        iOperateProductTypeManageDao.batchDeleteRelatedData(dto.getAssignmentProcId());

        // 保存特殊操作日志
        OperateUserInfoPO operateUserInfoPO = iOperateProductTypeManageDao.getOperateUserPO(dto.getMyUserName());
        OperationSpecialLogPO operationSpecialLogPO = new OperationSpecialLogPO();
        operationSpecialLogPO.setLogId(LogicIdUtil.bussinessId());
        operationSpecialLogPO.setOuterId(dto.getAssignmentProcId());
        operationSpecialLogPO.setAccount(operateUserInfoPO.getUserName());
        operationSpecialLogPO.setRealName(operateUserInfoPO.getRealName());
        operationSpecialLogPO.setIp(dto.getIp());
        operationSpecialLogPO.setFunctionType(5);
        operationSpecialLogPO.setOperateFunction(dto.getOperateFunction());
        operationSpecialLogPO.setOperateDec(operateUserInfoPO.getRealName() + " 删除数据");
        operationSpecialLogPO.setOperateWay(dto.getOperateWay());
        operationSpecialLogPO.setStatus(DataStatusEnum.NORMAL.getType());
        operationSpecialLogPO.setCreateTime(nowTime);
        operationSpecialLogPO.setUpdateTime(nowTime);
        iOperateProductTypeManageDao.save(SqlUtil.durableData(operationSpecialLogPO, PlatformConstants.TABLE_SAVE));

        return count;
    }

    /**
     * <desc>
     *      添加或者更新产品类型
     * </desc>
     *
     * @param dto 产品类型dto
     * @return
     * @author pengwei
     * @createDate 2020/12/03
     */
    @Transactional(rollbackFor = Exception.class,propagation = Propagation.REQUIRED)
    public MessageVO saveOrUpdate(OperateProductTypeManageGetDTO dto) throws Exception{
        Date  nowTime  =  new Date();
        //是否存在相同的产品名称
//        int   sameCnt  =  iOperateProductTypeManageDao.querySameProductNameCnt(dto.getAssignmentProcId(),dto.getProductName(), dto.getFeeType());
//        if(sameCnt>0){
//            return new MessageVO(OperateErrorCodeEnum.OPERATE_PRODUCT_TYPE_PRODUCT_NAME_EXIST_ERR.getErrorCode());
//        }
        //是否存在相同的匹配顺序
        int   sameOrder  =  iOperateProductTypeManageDao.querySameOrderCnt(dto.getAssignmentProcId(),String.valueOf(dto.getOrder()), dto.getFeeType());
        if(sameOrder>0){
            return new MessageVO(OperateErrorCodeEnum.OPERATE_PRODUCT_TYPE_ORDER_EXIST_ERR.getErrorCode());
        }
        String title  = "";
        if(StringUtils.isNotEmpty(dto.getAssignmentProcId())){
            title ="修改";
            this.update(dto,nowTime);
            //批量删除中间表
            iOperateProductTypeManageDao.batchDeleteRelatedData(dto.getAssignmentProcId());
        }else{
            title="添加";
            dto.setAssignmentProcId(LogicIdUtil.bussinessId());
            this.save(dto,nowTime);
        }
        //构造产品类型和产品编码的关系列表
        List<AssignmentProductModelRelationPO>     apmrList  = new ArrayList<>();
        String   relatedProcModels  =   dto.getRelatedProModels();
        if(StringUtils.isNotEmpty(relatedProcModels)){
            JSONArray   ja  =  JSONArray.parseArray(relatedProcModels);
            for(int i=0;i<ja.size();i++){
                AssignmentProductModelRelationPO   apmr  =  new  AssignmentProductModelRelationPO();
                JSONObject   jo   =  ja.getJSONObject(i);
                String  modelId =  jo.getString("modelId");
                String  calculateAmount =  jo.getString("calculateAmount");
                String  calculateTimes =  jo.getString("calculateTimes");

                apmr.setModelId(modelId);
                apmr.setAssignmentProcId(dto.getAssignmentProcId());
                apmr.setCalculateAmount(Integer.valueOf(calculateAmount));
                apmr.setCalculateTimes(Integer.valueOf(calculateTimes));
                apmr.setCreateTime(nowTime);
                apmr.setUpdateTime(nowTime);
                apmr.setStatus(DataStatusEnum.NORMAL.getType());
                apmr.setCreateUserId(dto.getMyUserName());
                apmr.setOperateUserId(dto.getMyUserName());
                apmrList.add(apmr);
            }
            //批量插入中间表
            if (!apmrList.isEmpty()){
                iOperateProductTypeManageDao.batchSaveProductTypeModelRelationData(apmrList);
            }
        }
        // 保存特殊操作日志
        OperateUserInfoPO operateUserInfoPO = iOperateProductTypeManageDao.getOperateUserPO(dto.getMyUserName());
        OperationSpecialLogPO operationSpecialLogPO = new OperationSpecialLogPO();
        operationSpecialLogPO.setLogId(LogicIdUtil.bussinessId());
        operationSpecialLogPO.setOuterId(dto.getAssignmentProcId());
        operationSpecialLogPO.setAccount(operateUserInfoPO.getUserName());
        operationSpecialLogPO.setRealName(operateUserInfoPO.getRealName());
        operationSpecialLogPO.setIp(dto.getIp());
        operationSpecialLogPO.setFunctionType(5);
        operationSpecialLogPO.setOperateFunction(dto.getOperateFunction());
        String descBuilder = operateUserInfoPO.getRealName() + " " +
                title + "数据，" +
                "收费类型为：" + FeeTypeEnum.getNameByType(dto.getFeeType()) +
                ",产品名称为：" + dto.getProductName() +
                ",收费标准为：" + dto.getFeeNorm() + FeeTypeEnum.getUnitByType(dto.getFeeType()) +
                ",匹配顺序为：" + dto.getOrder();
        operationSpecialLogPO.setOperateDec(descBuilder);
        operationSpecialLogPO.setOperateData(JSON.toJSONString(dto));
        operationSpecialLogPO.setOperateWay(dto.getOperateWay());
        operationSpecialLogPO.setStatus(DataStatusEnum.NORMAL.getType());
        operationSpecialLogPO.setCreateTime(nowTime);
        operationSpecialLogPO.setUpdateTime(nowTime);
        iOperateProductTypeManageDao.save(SqlUtil.durableData(operationSpecialLogPO, PlatformConstants.TABLE_SAVE));
        return new MessageVO(BaseErrorCodeEnum.SUCCESS.getErrorCode());
    }

    /**
     * <desc>
     *      更新
     * </desc>
     *
     * @param dto 产品类型dto
     * @param nowTime 时间nowTime
     * @return
     * @author pengwei
     * @createDate 2020/12/03
     */
    private  Integer   update(OperateProductTypeManageGetDTO dto,Date  nowTime ) throws  Exception{
        // 构造产品类型信息数据
        OperateProductTypeManageGetVO  vo  = iOperateProductTypeManageDao.getOne(dto);
        AssignmentProductInfoPO   api   = new AssignmentProductInfoPO();
        api.setAssignmentProcId(dto.getAssignmentProcId());
        api.setFeeType(dto.getFeeType());
        api.setProductName(StringUtils.isNotEmpty(dto.getProductName())?dto.getProductName():vo.getProductName());
        api.setFeeNorm(dto.getFeeNorm());
        api.setFeeUnit(dto.getFeeUnit());
        api.setEquipUnit(dto.getEquipUnit());
        api.setOrder(dto.getOrder());
        api.setUpdateTime(nowTime);
        api.setOperateUserId(dto.getMyUserName());
        api.setStatus(DataStatusEnum.NORMAL.getType());
        Integer   count  =  iOperateProductTypeManageDao.update(SqlUtil.durableData(api, PlatformConstants.TABLE_UPDATE));
        return   count;
    }

    /**
     * <desc>
     *      新增
     * </desc>
     *
     * @param dto 产品类型dto
     * @param nowTime 时间nowTime
     * @return
     * @author pengwei
     * @createDate 2020/12/03
     */
    private  Integer  save(OperateProductTypeManageGetDTO  dto,Date  nowTime ) throws  Exception{
        // 构造产品类型信息数据
        AssignmentProductInfoPO   api   = new AssignmentProductInfoPO();
        api.setAssignmentProcId(dto.getAssignmentProcId());
        api.setFeeType(dto.getFeeType());
        api.setProductName(dto.getProductName());
        api.setFeeNorm(dto.getFeeNorm());
        api.setFeeUnit(dto.getFeeUnit());
        api.setEquipUnit(dto.getEquipUnit());
        api.setOrder(dto.getOrder());
        api.setCreateTime(nowTime);
        api.setUpdateTime(nowTime);
        api.setCreateUserId(dto.getMyUserName());
        api.setOperateUserId(dto.getMyUserName());
        api.setStatus(DataStatusEnum.NORMAL.getType());
        Integer  count = iOperateProductTypeManageDao.save(SqlUtil.durableData(api, PlatformConstants.TABLE_SAVE));
        return   count;
    }

    /**
     * <desc>
     *      获取产品类型相关产品型号列表
     * </desc>
     *
     * @return 标准格式化响应结果
     * @author pengwei
     * @createDate 2020/12/03
     */
    @Override
    public   Page<OperateAssignProductModelRelationGetVO> getRelatedProcModelPage(OperateProductTypeManageGetDTO dto) throws Exception{
        if (StringUtils.isBlank(dto.getOrderColumn())) {
            dto.setOrderColumn("createTime");
            dto.setOrderRule("DESC");
        }
        Map<String, Object> params = SqlUtil.convertBeanToMapParams(dto);
        Page<OperateAssignProductModelRelationGetVO> page = new Page<>();
        page.getPage().setPageSize(dto.getPageSize());
        page.getPage().setCurrentPage(dto.getCurrentPage());
        params.put("startSlip", page.getPage().getStartSlip());
        params.put("pageSize", page.getPage().getPageSize());
        List<OperateAssignProductModelRelationGetVO> vOList = iOperateProductTypeManageDao.getRelatedProcModelPage(params);
        this.assembleModelData(vOList);
        page.setRows(vOList, iOperateProductTypeManageDao.getRelatedProcModelRecordCount(params));
        return page;
    }


    /**
     * <desc>
     *      获取产品类型相关产品型号列表
     * </desc>
     *
     * @return 标准格式化响应结果
     * @author pengwei
     * @createDate 2020/12/03
     */
    public  Page<OperateAssignProductModelRelationGetVO> getProcModelPage(OperateProductTypeManageGetDTO dto) throws Exception{
        Map<String, Object> params = SqlUtil.convertBeanToMapParams(dto);
        Page<OperateAssignProductModelRelationGetVO> page = new Page<>();
        page.getPage().setPageSize(dto.getPageSize());
        page.getPage().setCurrentPage(dto.getCurrentPage());
        params.put("startSlip", page.getPage().getStartSlip());
        params.put("pageSize", page.getPage().getPageSize());
        page.setRows(iOperateProductTypeManageDao.getProcModelPage(params), iOperateProductTypeManageDao.getProcModelRecordCount(params));
        return page;
    }

    /**
     * <desc>
     *      获取产品类型下的产品信息列表
     * </desc>
     *
     * @param productType 产品类型 1电梯类2门禁类 3人脸类 4对讲类
     * @return
     * @Author Zhu.yj
     * @createDate  2021/2/22
     */
    @Override
    public List<Map<String, Object>> getAssignmentTypeList(String productType) throws Exception {
        return iOperateProductTypeManageDao.getAssignmentTypeList(productType);
    }

    /**
     * <desc>
     *      组装产品型号数据
     * </desc>
     *
     * @param
     * @return
     * @Author Zhu.yj
     * @createDate  2021/3/25
     */
    private void assembleModelData(List<OperateAssignProductModelRelationGetVO> relationList){
        //将产品型号数据组装成对象返回
        for (OperateAssignProductModelRelationGetVO relationGetVO : relationList){
            List<String> modelIdList = StringHandlerUtil.splitStringList(relationGetVO.getModelId());
            List<String> productNameList = StringHandlerUtil.splitStringList(relationGetVO.getProductName());
            List<String> productModelList = StringHandlerUtil.splitStringList(relationGetVO.getProductModel());
            List<Map<String, Object>> productModelInfoList = new ArrayList<>();
            for (int i = 0; i< modelIdList.size(); i++){
                Map<String, Object> productModelInfoMap = new HashMap<>();
                productModelInfoMap.put("modelId", modelIdList.get(i));
                productModelInfoMap.put("productName", productNameList.get(i));
                productModelInfoMap.put("productModel", productModelList.get(i));
                productModelInfoList.add(productModelInfoMap);
            }
            relationGetVO.setProductModelList(productModelInfoList);
        }
    }

}
